#include "ComponentsHolder.h"
#include <iostream>
//#include "../DataBase/PlacementGenerator.h"
#include "SimulationParameters.h"
using namespace std;
static ComponentsHolder* _holder = 0;
ComponentsHolder::ComponentsHolder(void)
{
	CacheManagement policy;
	if (SimulationParameters::CachePolicy == "FIFO")
		policy = FIFO;
	else if (SimulationParameters::CachePolicy == "LRU")
		policy = LRU;
	else
	{
		std::cout << "Fashla with Policy\n";
		throw "Fashla with Policy";
	}
	_handler = new EventsHandler();
	_cache = new Cache(SimulationParameters::CacheSize, SimulationParameters::CacheReadPart, 100-SimulationParameters::CacheReadPart, policy);
	_flashCache = new FlashCache(SimulationParameters::FlashSize, SimulationParameters::CacheReadPart, 100-SimulationParameters::CacheReadPart, policy);
	//_storage = new Storage();
	_parser = new Parser();
	_statistics = new StatisticsHandler();
	//_aggregatedStatistics = new AggregatedStatisticsHandler(SimulationParameters::AggregatedFile);
	//_placementGenerator = new PlacementGenerator(SimulationParameters::AllFiles);
	double size = SimulationParameters::FlashSize * MB;
	size = size / FlashAlignment;
	_flashDevice = new FlashDevice(size);
}


ComponentsHolder::~ComponentsHolder(void)
{
	
}

void ComponentsHolder::clear(){
	ifstream a(SimulationParameters::AggregatedFile);
	a.close();
	delete _handler;
	delete _cache;
	delete _flashCache;
	//delete _storage;
	delete _parser;
	delete _statistics;
	//delete _aggregatedStatistics;
//	if (_placementGenerator)
//		delete _placementGenerator;
	delete _flashDevice;
	delete _holder;

	_holder=0;
}


ComponentsHolder* ComponentsHolder::getInstance()
{
	if (_holder == 0)
		_holder = new ComponentsHolder();
	return _holder;
}



EventsHandler* ComponentsHolder::getEventsHandler()
{
	return _handler;
}
Cache* ComponentsHolder::getCache()
{
	return _cache;
}
Cache* ComponentsHolder::getFlashCache()
{
	return _flashCache;
}
/*
Storage* ComponentsHolder::getStorage(){
	if (_storage == 0)
		_storage = new Storage();
	return _storage;
}
*/
void ComponentsHolder::setCache(Cache* c)
{
	_cache = c;
}

Parser* ComponentsHolder::getParser()
{
	return _parser;
}

StatisticsHandler* ComponentsHolder::getStatisticsHandler()
{
	return _statistics;
}

/*
AggregatedStatisticsHandler* ComponentsHolder::getAggregatedStatisticsHandler()
{
	return _aggregatedStatistics;
}
*/
/*
PlacementGenerator* ComponentsHolder::getPlacementGenerator()
{
	if (_placementGenerator == 0)
		_placementGenerator = new PlacementGenerator(SimulationParameters::AllFiles);
	return _placementGenerator;
}
*/




LUN* ComponentsHolder::getLUN(int lunID)
{
	map<int,LUN*>::iterator it = _luns.find(lunID);
	if (it != _luns.end())
		return it->second;
	return NULL;
}

void ComponentsHolder::addLUN(int lunID, int group)
{
	map<int,LUN*>::iterator it = _luns.find(lunID);
	if (it == _luns.end())
		_luns.insert(pair<int,LUN*>(lunID, new LUN(lunID, group)));
}

FlashDevice* ComponentsHolder::getFlashDevice()
{
	return _flashDevice;
}